/*
@file      Lattice.c
@brief     手把手教你51单片机 第七章课后习题第6题[官方答案]
@author    青岛金思特电子有限公司 (https://www.qdkingst.com/cn)
*/

#include <reg52.h>

sbit ADDR0 = P1^0;
sbit ADDR1 = P1^1;
sbit ADDR2 = P1^2;
sbit ADDR3 = P1^3;
sbit ENLED = P1^4;

void main()
{
    EA = 1;       //使能总中断
    ENLED = 0;    //使能LED
    TMOD = 0x01;  //设置T0为模式1
    TH0  = 0xFC;  //为T0赋初值0xFC67，定时1ms
    TL0  = 0x67;
    ET0  = 1;     //使能T0中断
    TR0  = 1;     //启动T0
    while (1);
}
/* 定时器0中断服务函数 */
void InterruptTimer0() interrupt 1
{
    static unsigned char i = 0;  //动态扫描的索引

    TH0 = 0xFC;  //重新加载初值
    TL0 = 0x67;
    //以下代码完成LED点阵动态扫描刷新
    P0 = 0xFF;   //显示消隐
    switch (i)
    {
        //点阵LED部分
        case 0: ADDR3 = 0; ADDR2=0; ADDR1=0; ADDR0=0; i++; P0=0; break;
        case 1: ADDR3 = 0; ADDR2=0; ADDR1=0; ADDR0=1; i++; P0=0; break;
        case 2: ADDR3 = 0; ADDR2=0; ADDR1=1; ADDR0=0; i++; P0=0; break;
        case 3: ADDR3 = 0; ADDR2=0; ADDR1=1; ADDR0=1; i++; P0=0; break;
        case 4: ADDR3 = 0; ADDR2=1; ADDR1=0; ADDR0=0; i++; P0=0; break;
        case 5: ADDR3 = 0; ADDR2=1; ADDR1=0; ADDR0=1; i++; P0=0; break;
        case 6: ADDR3 = 0; ADDR2=1; ADDR1=1; ADDR0=0; i++; P0=0; break;
        case 7: ADDR3 = 0; ADDR2=1; ADDR1=1; ADDR0=1; i++; P0=0; break;
        //数码管部分
        case 8:  ADDR3 = 1; ADDR2=0; ADDR1=0; ADDR0=0; i++; P0=0; break;
        case 9:  ADDR3 = 1; ADDR2=0; ADDR1=0; ADDR0=1; i++; P0=0; break;
        case 10: ADDR3 = 1; ADDR2=0; ADDR1=1; ADDR0=0; i++; P0=0; break;
        case 11: ADDR3 = 1; ADDR2=0; ADDR1=1; ADDR0=1; i++; P0=0; break;
        case 12: ADDR3 = 1; ADDR2=1; ADDR1=0; ADDR0=0; i++; P0=0; break;
        case 13: ADDR3 = 1; ADDR2=1; ADDR1=0; ADDR0=1; i++; P0=0; break;
        //独立LED部分
        case 14: ADDR3 = 1; ADDR2=1; ADDR1=1; ADDR0=0; i=0; P0=0; break;
        default: break;
    }
}